package com.tally.project.system.user.service;

import com.tally.common.constant.Constants;
import com.tally.common.constant.UserConstants;
import com.tally.common.utils.CodeUtils;
import com.tally.common.utils.DateUtils;
import com.tally.common.utils.StringUtils;
import com.tally.framework.web.AjaxResult;
import com.tally.project.system.user.domain.User;
import com.tally.project.system.user.mapper.UserMapper;
import org.apache.ibatis.annotations.Param;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;

/**
 * 用户 业务层处理
 * @author soul
 */
@Service
public class UserServiceImpl implements IUserService
{
    private static final Logger log = LoggerFactory.getLogger(UserServiceImpl.class);

    @Resource
    private UserMapper userMapper;

    @Resource
    private RedisTemplate redisTemplate;

    @Override
    public User loadUserByUsername(@Param("username") String username) {
        return userMapper.loadUserByUsername(username);
    }

    /**
     * 注册
     * @param user
     * @return
     */
    @Override
    public AjaxResult register(User user) {
        // 验证邮箱格式
        if (!CodeUtils.isEmail(user.getEmail())){
            return AjaxResult.error("邮箱格式有误！");
        }

        // 获取Redis缓存信息
        Object obj = redisTemplate.opsForValue().get(Constants.CACHE_REGISTER + user.getEmail());
        if (obj == null) {
            return AjaxResult.error("请重新获取验证码！");
        } else if (!Integer.valueOf(String.valueOf(obj)).equals(user.getCode())) {
            return AjaxResult.error("验证码错误！");
        }

        String msg = "", loginName = user.getLoginName(), password = user.getPassword();
        if (StringUtils.isEmpty(loginName)) {
            msg = "用户名不能为空";
        }
        if (StringUtils.isEmpty(password)) {
            msg = "用户密码不能为空";
        }
        if (password.length() < UserConstants.PASSWORD_MIN_LENGTH || password.length() > UserConstants.PASSWORD_MAX_LENGTH) {
            msg = "密码长度必须在5到20个字符之间";
        }
        if (loginName.length() < UserConstants.USERNAME_MIN_LENGTH || loginName.length() > UserConstants.USERNAME_MAX_LENGTH) {
            msg = "账户长度必须在2到20个字符之间";
        }
        if (userMapper.checkLoginNameUnique(loginName) > UserConstants.USER_NAME_UNIQUE) {
            msg = "用户名已存在";
        }
        if (StringUtils.isNotEmpty(user.getEmail()) && UserConstants.USER_EMAIL_NOT_UNIQUE.equals(checkEmailUnique(user))) {
            msg = "邮箱账号已存在";
        }
        if (msg.isEmpty()){
            // 恢复状态码
            user.setStatus(0);
            // 创建密码加密的对象
            BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
            // 密码加密
            user.setPassword(passwordEncoder.encode(password));
            // 密码更新时间
            user.setPwdUpdateDate(DateUtils.getNowDate());
            // 创建时间
            user.setCreateTime(System.currentTimeMillis());
            // 保存用户
            boolean regFlag = userMapper.insertUser(user) > 0;
            if (!regFlag)
            {
                msg = "注册失败,请联系系统管理人员";
            }else {
                return AjaxResult.success("注册成功");
            }
        }
        return AjaxResult.error(msg);
    }

    /**
     * 忘记密码
     * @param user
     * @return
     */
    @Override
    public AjaxResult forget(User user) {
        int code = user.getCode();
        String msg = "", loginName = user.getLoginName(), password = user.getPassword();
        if (StringUtils.isEmpty(loginName)) {
            msg = "用户名不能为空";
        }
        if (StringUtils.isEmpty(password)) {
            msg = "用户密码不能为空";
        }
        if (password.length() < UserConstants.PASSWORD_MIN_LENGTH || password.length() > UserConstants.PASSWORD_MAX_LENGTH) {
            msg = "密码长度必须在5到20个字符之间";
        }

        if (!msg.isEmpty()){
            return AjaxResult.error(msg);
        }

        user = userMapper.loadUserByUsername(loginName);
        if (user == null){
            return AjaxResult.error("用户不存在！");
        }
        if (user.getEmail() == null || user.getEmail().isEmpty()){
            return AjaxResult.error("该用户未绑定邮箱！");
        }
        // 验证邮箱格式
        if (!CodeUtils.isEmail(user.getEmail())){
            return AjaxResult.error("邮箱格式有误！");
        }

        // 获取Redis缓存信息
        Object obj = redisTemplate.opsForValue().get(Constants.CACHE_FORGET + user.getEmail());
        if (obj == null) {
            return AjaxResult.error("请重新获取验证码！");
        } else if (!Integer.valueOf(String.valueOf(obj)).equals(code)) {
            return AjaxResult.error("验证码错误！");
        }

        // 创建密码加密的对象
        BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
        // 密码加密
        user.setPassword(passwordEncoder.encode(password));
        // 密码更新时间
        user.setPwdUpdateDate(DateUtils.getNowDate());

        // 保存用户
        boolean regFlag = userMapper.updateUser(user) > 0;
        if (!regFlag) {
            return AjaxResult.success("操作失败,请联系系统管理人员");
        } else {
            return AjaxResult.success("操作成功");
        }
    }

    /**
     * 校验email是否唯一
     *
     * @param user 用户信息
     * @return
     */
    public String checkEmailUnique(User user)
    {
        Long userId = StringUtils.isNull(user.getUserId()) ? -1L : user.getUserId();
        User info = userMapper.checkEmailUnique(user.getEmail());
        if (StringUtils.isNotNull(info) && info.getUserId().longValue() != userId.longValue())
        {
            return UserConstants.USER_EMAIL_NOT_UNIQUE;
        }
        return UserConstants.USER_EMAIL_UNIQUE;
    }
}
